from flask_sqlalchemy.query import Query
from .models import db

def select(self, *cols, **aliases):
    if not cols and not aliases:
        ret = vars(self)
        if hasattr(self, '__props__'):
            for prop in self.__props__:
                ret[prop] = self.__getattribute__(prop)
        if hasattr(self, '__rel__'):
            for rel in self.__rel__:
                if rel in ret:
                    del ret[rel]
        del ret['_sa_instance_state']
        return ret
    ret = {}
    for col in cols:
        ret[col] = self.__getattribute__(col)
    for k, v in aliases.items():
        ret[v] = self.__getattribute__(k)
    return ret

def ignore(self, *cols):
    ret = self.select()
    for col in cols:
        del ret[col]
    return ret

def update(self, commit=True, **kwargs):
    for k, v in kwargs.items():
        self.__setattr__(k, v)
    if commit:
        db.session.commit()

def insert(self, commit=True):
    db.session.add(self)
    if commit:
        db.session.commit()
    return self

db.Model.select = select
db.Model.ignore = ignore
db.Model.update = update
db.Model.insert = insert

def select_many(self, *cols, **aliases):
    return map(lambda this: this.select(*cols, **aliases), self)

def update_many(self, commit=True, **kwargs):
    for i in self:
        i.update(False, **kwargs)
    if commit:
        db.session.commit()

Query.select = select_many
Query.selects = lambda self, *cols, **aliases: list(self.select(*cols, **aliases))
Query.update = update_many